package com.insigma.business.common.config;

import com.insigma.business.qrcode.common.util.*;
import com.insigma.business.qrcode.common.vo.RestfulResult;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpStatus;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.web.HttpMediaTypeNotSupportedException;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.servlet.NoHandlerFoundException;


@ControllerAdvice
@ResponseBody
public class ExceptionAdvice {

    private static final Logger logger = LoggerFactory.getLogger(ExceptionAdvice.class);

    
    @ResponseStatus(HttpStatus.BAD_REQUEST)
    @ExceptionHandler(HttpMessageNotReadableException.class)
    public RestfulResult handleHttpMessageNotReadableException(final HttpMessageNotReadableException e) {
        ExceptionUtil.caught(logger,e,"参数解析失败");
        return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR, HttpStatus.BAD_REQUEST.value() + "|" + HttpStatus.BAD_REQUEST.getReasonPhrase());
    }

    
    @ResponseStatus(HttpStatus.METHOD_NOT_ALLOWED)
    @ExceptionHandler(HttpRequestMethodNotSupportedException.class)
    public RestfulResult handleHttpRequestMethodNotSupportedException(final HttpRequestMethodNotSupportedException e) {
        ExceptionUtil.caught(logger,e,"不支持当前请求方法");
        return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR, HttpStatus.METHOD_NOT_ALLOWED.value() + "|" + HttpStatus.METHOD_NOT_ALLOWED.getReasonPhrase());
    }

    
    @ResponseStatus(HttpStatus.UNSUPPORTED_MEDIA_TYPE)
    @ExceptionHandler(HttpMediaTypeNotSupportedException.class)
    public RestfulResult handleHttpMediaTypeNotSupportedException(final Exception e) {
        ExceptionUtil.caught(logger,e,"不支持当前媒体类型");
        return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR, HttpStatus.UNSUPPORTED_MEDIA_TYPE.value() + "|" + HttpStatus.UNSUPPORTED_MEDIA_TYPE.getReasonPhrase());
    }

    @ResponseStatus(HttpStatus.OK)
    @ExceptionHandler(BizException.class)
    public RestfulResult handleBizExceptionException(final Exception e) {
        ExceptionUtil.caught(logger,e,"业务异常");
        return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR, e.getMessage());
    }

    
    @ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
    @ExceptionHandler(Exception.class)
    public RestfulResult handleException(final Exception e) {
        if (e instanceof NoHandlerFoundException) {
            ExceptionUtil.caught(logger, e, "访问的URI资源不存在");
            return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR,
                    HttpStatus.INTERNAL_SERVER_ERROR.value() + "|" + "访问的URI资源不存在，请联系管理员");
        } else if (e instanceof AccessFailedException) {
            ExceptionUtil.caught(logger, e, " 访问出错，错误码为", ((AccessFailedException) e).getErrCode());
            return RestfulResultUtil.buildFailed(RestfulCodeEnum.getByEnumCode(((AccessFailedException) e).getErrCode()), e.getMessage() != null?e.getMessage():
                    HttpStatus.INTERNAL_SERVER_ERROR.value() + "|" + "访问出错，请联系管理员");
        } else if (e instanceof BizException) {
            final BizException be = (BizException) e;
            ExceptionUtil.caught(logger, e, " 访问出错，错误信息为:",(be.getResultScenarioEnum()!=null?be.getResultScenarioEnum().toString():
                    StringUtils.EMPTY)+"|"+be.getErrorCodeEnum().toString()+"|"+e.getMessage());
            return RestfulResultUtil.buildFailed(RestfulCodeEnum.getByEnumCode(((BizException) e).getErrorCodeEnum().getCode()), e.getMessage() != null?e.getMessage():
                    HttpStatus.INTERNAL_SERVER_ERROR.value() + "|" + "访问出错，请联系管理员");
        } else {
            ExceptionUtil.caught(logger, e, e.getMessage());
            return RestfulResultUtil.buildFailed(RestfulCodeEnum.INTERNAL_ERROR,
                    HttpStatus.INTERNAL_SERVER_ERROR.value() + "|" + "服务器在偷懒,请迅速举报给客服");
        }
    }
}
